home *** CD-ROM | disk | FTP | other *** search
- /*
- ** Apple Macintosh Developer Technical Support
- **
- ** Program: buttonscontrol.c
- ** Written by: Eric Soldan
- **
- ** Copyright © 1993 Apple Computer, Inc.
- ** All rights reserved.
- */
-
- /* You may incorporate this sample code into your applications without
- ** restriction, though the sample code has been provided "AS IS" and the
- ** responsibility for its operation is 100% yours. However, what you are
- ** not permitted to do is to redistribute the source as "DSC Sample Code"
- ** after having made changes. If you're going to re-distribute the source,
- ** we require that you make it clear in the source that the code was
- ** descended from Apple Sample Code, but that you've made changes. */
-
-
-
- /*****************************************************************************/
-
-
-
- #ifndef __CONTROLS__
- #include <Controls.h>
- #endif
-
- #ifndef __ERRORS__
- #include <Errors.h>
- #endif
-
- #ifndef __FONTS__
- #include <Fonts.h>
- #endif
-
- #ifndef __MEMORY__
- #include <Memory.h>
- #endif
-
- #ifndef __RESOURCES__
- #include <Resources.h>
- #endif
-
- #ifndef __OSUTILS__
- #include <OSUtils.h>
- #endif
-
- #ifndef __SCRIPT__
- #include <Script.h>
- #endif
-
- #ifndef __STRINGUTILS__
- #include "StringUtils.h"
- #endif
-
- #ifndef __UTILITIES__
- #include "Utilities.h"
- #endif
-
- #ifndef __TEXTEDIT__
- #include <TextEdit.h>
- #endif
-
-
-
- /*****************************************************************************/
-
-
-
- void DebugWindow(Str255 str);
-
- static pascal long ButtonsCtl(short varCode, ControlHandle ctl, short msg, long parm);
- void InitButtonsCtl(short viewID);
- Boolean IsButtonsCtl(ControlHandle ctl);
- static pascal void NoRect(GrafVerb verb, Rect *r);
- static void GetRects(Rect rct, Rect *tr, Rect *r);
-
- #ifdef powerc
- #pragma options align=mac68k
- #endif
- typedef struct cdefRsrcJMP {
- long jsrInst;
- long mmemInst;
- short mregInst;
- short beqInst;
- short jmpInst;
- long jmpAddress;
- } cdefRsrcJMP;
- typedef cdefRsrcJMP *cdefRsrcJMPPtr, **cdefRsrcJMPHndl;
- #ifdef powerc
- #pragma options align=reset
- #endif
-
- static cdefRsrcJMPHndl gButtonsCDEF;
-
-
-
- /*****************************************************************************/
- /*****************************************************************************/
-
-
-
- #pragma segment Controls
- static pascal long ButtonsCtl(short varCode, ControlHandle ctl, short msg, long parm)
- {
- Rect rct, r, tr;
- WindowPtr ww;
- short txFont, txSize, txMode, ascent, i, dev;
- Style txFace;
- FontInfo finfo;
- Str255 str;
- QDProcs qdp;
- QDProcsPtr oldqdp;
- RgnHandle oldClip, bwClip, clClip;
- RGBColor oldrgb;
-
- static QDRectUPP qdrupp;
- static RGBColor grayrgb = {0x8000, 0x8000, 0x8000};
-
- rct = (*ctl)->contrlRect;
- GetPort(&ww);
-
- switch (msg) {
-
- case drawCntl:
- txFont = ww->txFont;
- txSize = ww->txSize;
- txFace = ww->txFace;
- txMode = ww->txMode;
- GetFontInfo(&finfo);
- ascent = (finfo.ascent - finfo.descent) / 2;
- if (!(varCode & 0x08)) {
- TextFont(systemFont);
- TextFace(normal);
- TextSize(0);
- ascent = 4;
- }
- switch (varCode & 0x07) {
- case checkBoxProc:
- case radioButProc:
- GetRects(rct, &tr, &r);
- GetFontInfo(&finfo);
- tr.bottom = tr.top + (tr.bottom - tr.top + 1) / 2;
- i = (finfo.ascent + finfo.descent);
- tr.bottom += (i / 2);
- tr.top = tr.bottom - i;
- pcpy(str, (*ctl)->contrlTitle);
-
- oldqdp = ww->grafProcs;
- if (oldqdp)
- BlockMove(oldqdp, &qdp, sizeof(QDProcs));
- else
- SetStdProcs(&qdp);
- if (!qdrupp) {
- #if USES68KINLINES
- qdrupp = (QDRectUPP)NoRect;
- #else
- qdrupp = NewQDRectProc(NoRect);
- #endif
- }
- qdp.rectProc = qdrupp;
- ww->grafProcs = &qdp;
-
- TextMode(srcOr);
- TETextBox(str + 1, str[0], &tr, teFlushDefault);
- TextMode(txMode);
- ww->grafProcs = oldqdp;
- GetClip(oldClip = NewRgn());
- if ((*ctl)->contrlHilite == 255) {
- bwClip = LocalScreenDepthRegion(1);
- clClip = LocalScreenDepthRegion(4);
- DiffRgn(bwClip, clClip, bwClip);
- SectRgn(bwClip, oldClip, bwClip);
- SectRgn(clClip, oldClip, clClip);
- }
- else {
- CopyRgn(oldClip, bwClip = NewRgn());
- clClip = NewRgn();
- }
- for (dev = 0; dev < 2; ++dev) {
- if (!dev) {
- if (EmptyRgn(bwClip)) continue;
- SetClip(bwClip);
- if ((*ctl)->contrlHilite == 255) PenPat((ConstPatternParam)&qd.gray);
- }
- if (dev) {
- if (EmptyRgn(clClip)) continue;
- SetClip(clClip);
- if ((*ctl)->contrlHilite == 255) {
- GetForeColor(&oldrgb);
- RGBForeColor(&grayrgb);
- }
- }
- if ((*ctl)->contrlHilite == 0x01) PenSize(2, 2);
- if ((varCode & 0x07) == radioButProc) {
- EraseOval(&r);
- FrameOval(&r);
- PenSize(1, 1);
- if ((*ctl)->contrlValue) {
- InsetRect(&r, 3, 3);
- PaintOval(&r);
- InsetRect(&r, -3, -3);
- }
- }
- else {
- EraseRect(&r);
- FrameRect(&r);
- PenSize(1, 1);
- if ((*ctl)->contrlValue) {
- MoveTo(r.left, r.top);
- LineTo(r.right - 1, r.bottom - 1);
- MoveTo(r.right - 1, r.top);
- LineTo(r.left, r.bottom - 1);
- }
- }
- if (dev)
- if ((*ctl)->contrlHilite == 255)
- RGBForeColor(&oldrgb);
- PenNormal();
- }
- SetClip(oldClip);
- DisposeRgn(oldClip);
- DisposeRgn(bwClip);
- DisposeRgn(clClip);
- break;
- }
- break;
-
- case testCntl:
- if ((*ctl)->contrlHilite == 255) return(0);
- /* Control disabled, so no click. We probably don't get called in this case. */
- return(PtInRect(*(Point *)&parm, &rct));
- break;
-
- case calcCRgns:
- case calcCntlRgn:
- case calcThumbRgn:
- if (msg == calcCRgns) parm &= 0x00FFFFFF;
- RectRgn((RgnHandle)parm, &rct);
- if (msg != calcCRgns) return(1);
- break;
-
- case initCntl:
- break;
-
- case dispCntl:
- break;
-
- case posCntl:
- break;
-
- case thumbCntl:
- break;
-
- case dragCntl:
- break;
-
- case autoTrack:
- break;
- }
-
- return(0);
- }
-
-
-
- /*****************************************************************************/
-
-
-
- #pragma segment Controls
- void InitButtonsCtl(short viewID)
- {
- static ControlDefUPP cdefupp;
-
- if (!gButtonsCDEF) {
- gButtonsCDEF = (cdefRsrcJMPHndl)GetResource('CDEF', (viewID / 16));
- if (gButtonsCDEF) {
- if (!cdefupp) {
- cdefupp = NewControlDefProc(ButtonsCtl);
- }
- (*gButtonsCDEF)->jmpAddress = (long)cdefupp;
- if (TrapExists(_HWPriv))
- FlushInstructionCache();
- /* Make sure that instruction caches don't kill us. */
- }
- }
- }
-
-
-
- /*****************************************************************************/
-
-
-
- #pragma segment Controls
- Boolean IsButtonsCtl(ControlHandle ctl)
- {
- if (ctl)
- if (StripAddress((*ctl)->contrlDefProc) == StripAddress(gButtonsCDEF))
- return(true);
- /* The handle may be locked, which means that the hi-bit
- ** may be on, thus invalidating the compare. Dereference the
- ** handles to get rid of this possibility. */
- return(false);
- }
-
-
-
- /*****************************************************************************/
-
-
-
- #pragma segment Controls
- static pascal void NoRect(GrafVerb verb, Rect *r)
- {
- #ifndef __MWERKS__
- #pragma unused (verb, r)
- #endif
- }
-
-
-
- /*****************************************************************************/
-
-
-
- #pragma segment Controls
- static void GetRects(Rect rct, Rect *tr, Rect *r)
- {
- *tr = *r = rct; /* Return text rect and indicator rect. */
- r->top = (r->top + (r->bottom - r->top + 1) / 2);
- r->top -= 6;
- r->bottom = r->top + 12;
- if (!GetSysDirection()) {
- r->left += 2;
- r->right = r->left + 12;
- tr->left += 17;
- }
- else {
- r->right -= 2;
- r->left = r->right - 12;
- tr->right -= 17;
- }
- }
-
-
-
-